//
//  DispatchQueue.swift
//  
//
//  Created by tangbl93 on 2021/2/25.
//

import Foundation

/// delay execute on main queue
public func yx_delay(_ seconds: Double = 2, closure: @escaping () -> ()) {
    DispatchQueue.main.yx_delay(seconds, closure: closure)
}

/// dispatch once
func yx_once(token: String = "\(#file):\(#function):\(#line)", closure: VoidClosure) {
    DispatchQueue.yx_once(token: token, closure: closure)
}

public extension DispatchQueue {
    
    /// dispatch once helper
    private static var _onceLock: NSLock = NSLock()
    private static var _onceToken: [String] = []
    
    /// delay execute
    func yx_delay(_ seconds: Double = 2, closure: @escaping VoidClosure) {
        let _t = DispatchTime.now() + Double(Int64(Double(NSEC_PER_SEC) * seconds)) / Double(NSEC_PER_SEC)
        asyncAfter(deadline: _t, execute: closure)
    }
    
    
    /// dispatch once
    static func yx_once(token: String = "\(#file):\(#function):\(#line)", closure: VoidClosure) {
        objc_sync_enter(_onceLock)
        defer {
            objc_sync_exit(_onceLock)
        }
        
        if _onceToken.contains(token) { return }
        
        _onceToken.append(token)
        closure()
    }
}
